<template>
  <div class="deploy-dialog-overlay" @click="handleOverlayClick">
    <div class="deploy-dialog" @click.stop>
      <div class="deploy-dialog-header">
        <h2>部署新应用</h2>
        <button @click="$emit('close')" class="close-btn">×</button>
      </div>
      
      <div class="deploy-dialog-content">
        <form @submit.prevent="handleDeploy" class="deploy-form">
          <!-- 应用基本信息 -->
          <div class="form-group">
            <label for="appName">应用名称:</label>
            <input 
              type="text" 
              id="appName" 
              v-model="formData.name" 
              required 
              placeholder="输入应用名称"
            >
          </div>

          <div class="form-group">
            <label for="dockerImage">Docker 镜像:</label>
            <div class="image-selector">
              <div class="image-input-container">
                <input 
                  type="text" 
                  id="dockerImage" 
                  v-model="formData.image" 
                  placeholder="搜索或输入镜像名称，例如: nginx:latest" 
                  required
                  @input="handleImageSearch"
                  @focus="showImageDropdown = true"
                  @blur="handleImageBlur"
                  @keydown="handleKeyDown"
                  autocomplete="off"
                >
                <button 
                  type="button" 
                  class="refresh-images-btn"
                  @click="refreshImages"
                  :disabled="loadingImages"
                  title="刷新镜像列表"
                >
                  <span v-if="loadingImages">⟳</span>
                  <span v-else>🔄</span>
                </button>
              </div>
              
              <!-- 镜像下拉列表 -->
              <div 
                v-if="showImageDropdown && (filteredImages.length > 0 || loadingImages)"
                class="image-dropdown"
              >
                <div v-if="loadingImages" class="loading-item">
                  <span class="loading-spinner">⟳</span>
                  加载镜像列表...
                </div>
                
                <div 
                  v-for="(image, index) in filteredImages" 
                  :key="image.fullName"
                  :class="['image-item', { 'selected': index === selectedImageIndex }]"
                  @mousedown="selectImage(image)"
                  @mouseenter="selectedImageIndex = index"
                >
                  <div class="image-info">
                    <div class="image-header">
                      <div class="image-name">{{ image.name }}</div>
                      <div class="image-meta">
                        <span class="image-size">{{ formatSize(image.size) }}</span>
                      </div>
                    </div>
                    <div class="image-tags">
                      <span 
                        v-for="tag in image.tags.slice(0, 4)" 
                        :key="tag"
                        class="tag"
                        @click.stop="selectImageWithTag(image.name, tag)"
                      >
                        {{ tag }}
                      </span>
                      <span v-if="image.tags.length > 4" class="more-tags">
                        +{{ image.tags.length - 4 }}
                      </span>
                    </div>
                  </div>
                </div>
                
                <div v-if="filteredImages.length === 0 && !loadingImages" class="no-images">
                  <div v-if="registryImages.length === 0">
                    <span>镜像仓库为空</span>
                    <small>请先上传镜像到仓库，或直接输入外部镜像名称</small>
                  </div>
                  <div v-else>
                    <span>未找到匹配的镜像</span>
                    <small>您可以直接输入镜像名称</small>
                  </div>
                </div>
              </div>
            </div>
          </div>

          <div class="form-group">
            <label for="replicas">副本数:</label>
            <input 
              type="number" 
              id="replicas" 
              v-model.number="formData.replicas" 
              min="1" 
              required
            >
          </div>

          <!-- 资源配置 -->
          <div class="row">
            <div class="form-group">
              <label for="cpu">CPU (Core):</label>
              <input
                type="text"
                id="cpu"
                v-model="formData.cpu"
                placeholder="例如: 0.5 或 500m"
                required
              >
            </div>
            <div class="form-group">
              <label for="memory">内存 (MiB/GiB):</label>
              <input
                type="text"
                id="memory"
                v-model="formData.memory"
                placeholder="例如: 512Mi 或 1Gi"
                required
              >
            </div>
          </div>

          <div class="form-group">
            <label for="storage">磁盘空间 (GiB):</label>
            <input
              type="text"
              id="storage"
              v-model="formData.storage"
              placeholder="例如: 10Gi (留空则不挂载存储)"
            >
          </div>

          <!-- 端口配置 -->
          <div class="form-group">
            <label>容器端口:</label>
            <div class="container-ports">
              <div 
                v-for="(port, index) in formData.containerPorts" 
                :key="index" 
                class="port-row"
              >
                <input 
                  type="number" 
                  v-model.number="formData.containerPorts[index]" 
                  placeholder="例如: 80" 
                  required
                >
                <button 
                  type="button" 
                  class="remove-btn" 
                  @click="removeContainerPort(index)"
                  :disabled="formData.containerPorts.length <= 1"
                >
                  -
                </button>
              </div>
            </div>
            <button type="button" @click="addContainerPort" class="add-btn">添加端口</button>
          </div>

          <!-- 服务类型 -->
          <div class="form-group">
            <label for="serviceType">服务类型:</label>
            <select id="serviceType" v-model="formData.serviceType">
              <option value="ClusterIP">ClusterIP</option>
              <option value="NodePort">NodePort</option>
              <option value="LoadBalancer">LoadBalancer</option>
            </select>
          </div>

          <!-- 端口映射 -->
          <div class="form-group">
            <label>端口映射 (容器端口 -> 服务端口):</label>
            <table class="port-mapping-table">
              <thead>
                <tr>
                  <th>容器端口</th>
                  <th>服务端口</th>
                  <th>操作</th>
                </tr>
              </thead>
              <tbody>
                <tr v-for="(mapping, index) in formData.portMappings" :key="index">
                  <td>
                    <input 
                      type="number" 
                      v-model.number="mapping.containerPort" 
                      placeholder="例如: 80" 
                      required
                    >
                  </td>
                  <td>
                    <input 
                      type="number" 
                      v-model.number="mapping.servicePort" 
                      placeholder="例如: 8080" 
                      required
                    >
                  </td>
                  <td>
                    <button 
                      type="button" 
                      class="remove-btn" 
                      @click="removePortMapping(index)"
                    >
                      -
                    </button>
                  </td>
                </tr>
              </tbody>
            </table>
            <button type="button" @click="addPortMapping" class="add-btn">添加映射</button>
          </div>

          <!-- 命名空间 -->
          <div class="form-group">
            <label for="namespace">命名空间:</label>
            <input 
              type="text" 
              id="namespace" 
              v-model="formData.namespace" 
              required
            >
          </div>

          <!-- 按钮组 -->
          <div class="dialog-actions">
            <button type="button" @click="$emit('close')" class="cancel-btn">
              取消
            </button>
            <button 
              type="submit" 
              class="deploy-btn" 
              :disabled="deploying"
            >
              {{ deploying ? '部署中...' : '立即部署' }}
            </button>
          </div>
        </form>

        <!-- 消息提示 -->
        <div 
          v-if="message.text" 
          :class="['message', message.type]"
        >
          {{ message.text }}
        </div>
      </div>
    </div>
  </div>
</template>

<script setup lang="ts">
import { ref, reactive, onMounted } from 'vue'
import axios from 'axios'
import { useAuthStore } from '@/stores/auth'

const authStore = useAuthStore()

// 定义事件
const emit = defineEmits<{
  close: []
  deployed: [app: any]
}>()

// 表单数据
const formData = reactive({
  name: '',
  image: '',
  replicas: 1,
  cpu: '500m',
  memory: '512Mi',
  storage: '',
  containerPorts: [80],
  serviceType: 'ClusterIP',
  portMappings: [{ containerPort: 80, servicePort: 8080 }],
  namespace: 'default'
})

// 状态管理
const deploying = ref(false)
const message = reactive({
  text: '',
  type: ''
})

// 镜像选择相关状态
const showImageDropdown = ref(false)
const loadingImages = ref(false)
const registryImages = ref<any[]>([])
const filteredImages = ref<any[]>([])
const imageSearchQuery = ref('')
const selectedImageIndex = ref(-1)

// 添加容器端口
const addContainerPort = () => {
  formData.containerPorts.push(80)
}

// 移除容器端口
const removeContainerPort = (index: number) => {
  if (formData.containerPorts.length > 1) {
    formData.containerPorts.splice(index, 1)
  }
}

// 添加端口映射
const addPortMapping = () => {
  formData.portMappings.push({ containerPort: 80, servicePort: 8080 })
}

// 移除端口映射
const removePortMapping = (index: number) => {
  formData.portMappings.splice(index, 1)
}

// 显示消息
const showMessage = (text: string, type: 'success' | 'error') => {
  message.text = text
  message.type = type

  // 3秒后自动清除消息
  setTimeout(() => {
    message.text = ''
    message.type = ''
  }, 3000)
}

// 获取镜像仓库列表
const fetchRegistryImages = async () => {
  try {
    loadingImages.value = true

    const response = await axios.get('/api/registry/images', {
      headers: {
        'Authorization': `Bearer ${authStore.token}`
      }
    })

    // 检查响应数据结构
    const images = response.data.data || response.data.images || []

    // 转换镜像数据格式
    registryImages.value = images.map((image: any) => ({
      name: image.name,
      tags: image.tags || ['latest'],
      fullName: `${image.name}:${image.tags?.[0] || 'latest'}`,
      size: image.size,
      created: image.createdAt || image.created
    }))

    // 初始化过滤列表
    filteredImages.value = registryImages.value
  } catch (error) {
    console.error('获取镜像列表失败:', error)
    // 静默失败，用户仍可手动输入
  } finally {
    loadingImages.value = false
  }
}

// 刷新镜像列表
const refreshImages = async () => {
  await fetchRegistryImages()
}

// 处理镜像搜索
const handleImageSearch = (event: Event) => {
  const target = event.target as HTMLInputElement
  const query = target.value.toLowerCase()
  imageSearchQuery.value = query

  if (query === '') {
    filteredImages.value = registryImages.value
  } else {
    filteredImages.value = registryImages.value.filter(image =>
      image.name.toLowerCase().includes(query) ||
      image.tags.some((tag: string) => tag.toLowerCase().includes(query))
    )
  }

  // 重置选中索引
  selectedImageIndex.value = -1
  showImageDropdown.value = true
}

// 选择镜像
const selectImage = (image: any) => {
  formData.image = image.fullName
  showImageDropdown.value = false
}

// 选择镜像和特定标签
const selectImageWithTag = (imageName: string, tag: string) => {
  formData.image = `${imageName}:${tag}`
  showImageDropdown.value = false
}

// 处理输入框失焦
const handleImageBlur = () => {
  // 延迟隐藏下拉框，以便点击事件能够触发
  setTimeout(() => {
    showImageDropdown.value = false
  }, 200)
}

// 格式化文件大小
const formatSize = (bytes: number) => {
  if (!bytes) return '未知'

  const sizes = ['B', 'KB', 'MB', 'GB']
  const i = Math.floor(Math.log(bytes) / Math.log(1024))
  return Math.round(bytes / Math.pow(1024, i) * 100) / 100 + ' ' + sizes[i]
}

// 处理键盘导航
const handleKeyDown = (event: KeyboardEvent) => {
  if (!showImageDropdown.value || filteredImages.value.length === 0) return

  switch (event.key) {
    case 'ArrowDown':
      event.preventDefault()
      selectedImageIndex.value = Math.min(selectedImageIndex.value + 1, filteredImages.value.length - 1)
      break
    case 'ArrowUp':
      event.preventDefault()
      selectedImageIndex.value = Math.max(selectedImageIndex.value - 1, -1)
      break
    case 'Enter':
      event.preventDefault()
      if (selectedImageIndex.value >= 0) {
        selectImage(filteredImages.value[selectedImageIndex.value])
      }
      break
    case 'Escape':
      showImageDropdown.value = false
      selectedImageIndex.value = -1
      break
  }
}

// 处理覆盖层点击
const handleOverlayClick = () => {
  emit('close')
}

// 处理部署
const handleDeploy = async () => {
  // 基本验证
  if (formData.containerPorts.length === 0) {
    showMessage('请至少指定一个容器端口。', 'error')
    return
  }

  if (formData.portMappings.length === 0) {
    showMessage('请至少添加一个端口映射。', 'error')
    return
  }

  deploying.value = true

  try {
    const deployData = {
      ...formData,
      storage: formData.storage || null,
      containerPorts: formData.containerPorts.filter(port => !isNaN(port)),
      portMappings: formData.portMappings.filter(mapping =>
        !isNaN(mapping.containerPort) && !isNaN(mapping.servicePort)
      )
    }

    const response = await axios.post('/api/deploy', deployData, {
      headers: {
        'Authorization': `Bearer ${authStore.token}`
      }
    })

    showMessage(`应用 "${formData.name}" 部署成功!`, 'success')

    // 通知父组件部署成功
    emit('deployed', deployData)

  } catch (error: any) {
    console.error('部署失败:', error)

    const errorMessage = error.response?.data?.message || error.message || '部署失败'
    showMessage(`部署失败: ${errorMessage}`, 'error')
  } finally {
    deploying.value = false
  }
}

// 组件挂载时获取镜像列表
onMounted(() => {
  fetchRegistryImages()
})
</script>

<style scoped>
/* 对话框覆盖层 */
.deploy-dialog-overlay {
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background: rgba(0, 0, 0, 0.5);
  display: flex;
  align-items: center;
  justify-content: center;
  z-index: 1000;
  padding: 20px;
}

/* 对话框主体 */
.deploy-dialog {
  background: white;
  border-radius: 12px;
  width: 100%;
  max-width: 800px;
  max-height: 90vh;
  overflow: hidden;
  box-shadow: 0 10px 40px rgba(0, 0, 0, 0.2);
  display: flex;
  flex-direction: column;
}

/* 对话框头部 */
.deploy-dialog-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 24px 30px;
  border-bottom: 1px solid #e5e7eb;
  background: #f8f9fa;
}

.deploy-dialog-header h2 {
  margin: 0;
  font-size: 24px;
  font-weight: 600;
  color: #1f2937;
}

.close-btn {
  background: none;
  border: none;
  font-size: 28px;
  color: #6b7280;
  cursor: pointer;
  padding: 0;
  width: 40px;
  height: 40px;
  display: flex;
  align-items: center;
  justify-content: center;
  border-radius: 6px;
  transition: all 0.2s;
}

.close-btn:hover {
  background: #e5e7eb;
  color: #374151;
}

/* 对话框内容 */
.deploy-dialog-content {
  flex: 1;
  overflow-y: auto;
  padding: 30px;
}

/* 表单样式 */
.deploy-form {
  display: flex;
  flex-direction: column;
  gap: 24px;
}

.form-group {
  display: flex;
  flex-direction: column;
  gap: 8px;
}

label {
  font-weight: 600;
  color: #374151;
  font-size: 14px;
}

input, select {
  padding: 12px 16px;
  border: 1px solid #d1d5db;
  border-radius: 8px;
  font-size: 14px;
  transition: all 0.2s;
}

input:focus, select:focus {
  outline: none;
  border-color: #3b82f6;
  box-shadow: 0 0 0 3px rgba(59, 130, 246, 0.1);
}

.row {
  display: flex;
  gap: 20px;
}

.row .form-group {
  flex: 1;
}

/* 镜像选择器样式 */
.image-selector {
  position: relative;
}

.image-input-container {
  display: flex;
  align-items: center;
  gap: 8px;
}

.image-input-container input {
  flex: 1;
}

.refresh-images-btn {
  padding: 12px;
  background-color: #f3f4f6;
  border: 1px solid #d1d5db;
  border-radius: 8px;
  cursor: pointer;
  font-size: 16px;
  transition: background-color 0.2s;
  min-width: 44px;
  display: flex;
  align-items: center;
  justify-content: center;
}

.refresh-images-btn:hover:not(:disabled) {
  background-color: #e5e7eb;
}

.refresh-images-btn:disabled {
  opacity: 0.5;
  cursor: not-allowed;
}

.refresh-images-btn .loading-spinner {
  animation: spin 1s linear infinite;
}

@keyframes spin {
  from { transform: rotate(0deg); }
  to { transform: rotate(360deg); }
}

.image-dropdown {
  position: absolute;
  top: 100%;
  left: 0;
  right: 0;
  background: white;
  border: 1px solid #d1d5db;
  border-radius: 8px;
  box-shadow: 0 4px 12px rgba(0, 0, 0, 0.15);
  max-height: 300px;
  overflow-y: auto;
  z-index: 1001;
  margin-top: 4px;
}

.loading-item {
  padding: 16px;
  text-align: center;
  color: #6b7280;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
}

.loading-item .loading-spinner {
  animation: spin 1s linear infinite;
}

.image-item {
  padding: 12px 16px;
  border-bottom: 1px solid #f3f4f6;
  cursor: pointer;
  transition: background-color 0.2s;
}

.image-item:hover,
.image-item.selected {
  background-color: #f8f9fa;
}

.image-item.selected {
  background-color: #e0f2fe;
  border-left: 3px solid #0369a1;
}

.image-item:last-child {
  border-bottom: none;
}

.image-info {
  display: flex;
  flex-direction: column;
  gap: 8px;
}

.image-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
}

.image-name {
  font-weight: 600;
  color: #1f2937;
  font-size: 14px;
  flex: 1;
}

.image-meta {
  display: flex;
  gap: 8px;
  align-items: center;
}

.image-size {
  font-size: 12px;
  color: #6b7280;
  background-color: #f3f4f6;
  padding: 2px 6px;
  border-radius: 4px;
}

.image-tags {
  display: flex;
  flex-wrap: wrap;
  gap: 4px;
  align-items: center;
}

.tag {
  background-color: #e0f2fe;
  color: #0369a1;
  padding: 2px 8px;
  border-radius: 12px;
  font-size: 12px;
  font-weight: 500;
  cursor: pointer;
  transition: background-color 0.2s;
}

.tag:hover {
  background-color: #bae6fd;
}

.more-tags {
  color: #6b7280;
  font-size: 12px;
  font-style: italic;
}

.no-images {
  padding: 20px;
  text-align: center;
  color: #6b7280;
}

.no-images small {
  display: block;
  margin-top: 4px;
  font-size: 12px;
  color: #9ca3af;
}

/* 容器端口样式 */
.container-ports {
  display: flex;
  flex-direction: column;
  gap: 10px;
  margin-bottom: 10px;
}

.port-row {
  display: flex;
  align-items: center;
  gap: 10px;
}

.port-row input {
  flex: 1;
}

/* 端口映射表格 */
.port-mapping-table {
  width: 100%;
  border-collapse: collapse;
  margin-bottom: 10px;
}

.port-mapping-table th,
.port-mapping-table td {
  border: 1px solid #d1d5db;
  padding: 12px;
  text-align: left;
}

.port-mapping-table th {
  background-color: #f8f9fa;
  font-weight: 600;
  color: #374151;
}

.port-mapping-table td input {
  width: 100%;
  margin: 0;
  border: none;
  padding: 8px;
}

.port-mapping-table td input:focus {
  box-shadow: none;
  border: 1px solid #3b82f6;
  border-radius: 4px;
}

/* 按钮样式 */
.add-btn, .remove-btn {
  padding: 8px 16px;
  border: none;
  border-radius: 6px;
  cursor: pointer;
  font-size: 14px;
  font-weight: 500;
  transition: background-color 0.2s;
}

.add-btn {
  background-color: #10b981;
  color: white;
}

.add-btn:hover {
  background-color: #059669;
}

.remove-btn {
  background-color: #ef4444;
  color: white;
  min-width: 32px;
}

.remove-btn:hover:not(:disabled) {
  background-color: #dc2626;
}

.remove-btn:disabled {
  background-color: #d1d5db;
  cursor: not-allowed;
}

/* 对话框操作按钮 */
.dialog-actions {
  display: flex;
  gap: 12px;
  justify-content: flex-end;
  padding-top: 20px;
  border-top: 1px solid #e5e7eb;
  margin-top: 20px;
}

.cancel-btn, .deploy-btn {
  padding: 12px 24px;
  border-radius: 8px;
  font-size: 16px;
  font-weight: 600;
  cursor: pointer;
  transition: all 0.2s;
  min-width: 120px;
}

.cancel-btn {
  background: #f3f4f6;
  border: 1px solid #d1d5db;
  color: #374151;
}

.cancel-btn:hover {
  background: #e5e7eb;
}

.deploy-btn {
  background: #3b82f6;
  border: 1px solid #3b82f6;
  color: white;
}

.deploy-btn:hover:not(:disabled) {
  background: #2563eb;
}

.deploy-btn:disabled {
  background: #9ca3af;
  border-color: #9ca3af;
  cursor: not-allowed;
}

/* 消息提示 */
.message {
  margin-top: 20px;
  padding: 16px;
  border-radius: 8px;
  text-align: center;
  font-weight: 500;
}

.message.success {
  background-color: #d1fae5;
  color: #065f46;
  border: 1px solid #a7f3d0;
}

.message.error {
  background-color: #fee2e2;
  color: #991b1b;
  border: 1px solid #fecaca;
}

/* 响应式设计 */
@media (max-width: 768px) {
  .deploy-dialog-overlay {
    padding: 10px;
  }

  .deploy-dialog {
    max-width: 100%;
  }

  .deploy-dialog-header {
    padding: 20px;
  }

  .deploy-dialog-content {
    padding: 20px;
  }

  .row {
    flex-direction: column;
  }

  .dialog-actions {
    flex-direction: column;
  }

  .cancel-btn, .deploy-btn {
    width: 100%;
  }
}
</style>
